/**
 * SUNING APPLIANCE CHAINS.
 * Copyright (c) 2012-2012 All Rights Reserved.
 */
package com.suning.sawp.web.controller;

import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.text.MessageFormat;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.ResponseStatus;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.suning.sawp.constants.ErrorCodeConstants;
import com.suning.sawp.dto.common.ReturnMsg;
import com.suning.sawp.exception.SawpException;
import com.suning.sawp.service.util.BaseContants;
import com.suning.sawp.web.exception.MyGsonView;

@Controller
public class DjBaseController extends com.suning.framework.web.controller.BaseController {
	private static final Logger LOGGER = LoggerFactory.getLogger(DjBaseController.class);

	private static final String CHAR_SET = "utf-8";

	public static final String TIMESTYLE = "yyyy-MM-dd HH:mm:ss.SSS";
	   private static final String SYSTEM_EXCEPTION = "SE";
	    private static final String BUSINESS_EXCEPTION = "BE";

	/**
	 * 
	 * 功能描述：获取请求参数
	 * 
	 * @param key
	 * @return 返回值
	 * @throw 异常描述
	 * @see 需要参见的其它内容
	 */
	protected String getParam(String key, HttpServletRequest request) {
		return request.getParameter(key);
	}

	/**
	 * 根据名字获取cookie
	 * 
	 * @param request
	 * @param key
	 *            cookie名字
	 * @return
	 */
	protected String getCookie(HttpServletRequest request, String key) {
		Map<String, Cookie> cookieMap = readCookieMap(request);
		if (cookieMap.containsKey(key)) {
			Cookie cookie = (Cookie) cookieMap.get(key);
			return cookie.getValue();
		} else {
			return null;
		}
	}

	/**
	 * 将cookie封装到Map里面
	 * 
	 * @param request
	 * @return
	 */
	private static Map<String, Cookie> readCookieMap(HttpServletRequest request) {
		Map<String, Cookie> cookieMap = new HashMap<String, Cookie>();
		Cookie[] cookies = request.getCookies();
		if (null != cookies) {
			for (Cookie cookie : cookies) {
				cookieMap.put(cookie.getName(), cookie);
			}
		}
		return cookieMap;
	}

	/**
	 * 对象转换成json
	 */
	protected String getJson(Object oj) {
		return gson.toJson(oj);
	}

	/**
	 * 
	 * 功能描述:将json数据写入响应头
	 * 
	 * @param obj
	 * @param response
	 * @see [相关类/方法](可选)
	 * @since [产品/模块版本](可选)
	 */
	protected void writeJsonToResponse(Object obj, HttpServletResponse response) {
		response.setCharacterEncoding(CHAR_SET);
		response.setHeader("Content-Language", "zh-CN");
		response.setContentType("application/json;charset=" + CHAR_SET);

		Gson gson = new GsonBuilder().disableHtmlEscaping().create();

		try {
			response.getOutputStream().print(gson.toJson(obj));
			response.getOutputStream().flush();
		} catch (UnsupportedEncodingException e) {
			LOGGER.error("writeJsonToResponse is error", e);
		} catch (IllegalStateException e2) {
			LOGGER.error("writeJsonToResponse is error", e2);
		} catch (IOException e3) {
			LOGGER.error("writeJsonToResponse is error", e3);
		}
	}

	/**
	 * 创建新的GsonView返回对象，并填充默认值
	 * 
	 * @return GsonView对象
	 */
	public MyGsonView createGsonView() {
		MyGsonView gsonView = new MyGsonView();
		gsonView.addStaticAttribute(BaseContants.RET_FLAG, BaseContants.SUCCESS);
		gsonView.addStaticAttribute(BaseContants.ERROR_CODE, StringUtils.EMPTY);
		gsonView.addStaticAttribute(BaseContants.ERROR_MSG, StringUtils.EMPTY);
		return gsonView;
	}

	/**
	 * 
	 * 功能描述: <br>
	 * 获取请求参数
	 * 
	 * @param key
	 * @param request
	 * @return
	 * @see [相关类/方法](可选)
	 * @since [产品/模块版本](可选)
	 */
	protected String getParameter(String key, HttpServletRequest request) {
		if ("".equalsIgnoreCase(key) || key == null) {
			return null;
		} else {
			return request.getParameter(key);
		}
	}

	protected Map<String, String> typeConvert(Map<?, ?> rawMap) {
		Map<String, String> paramMap = new HashMap<String, String>();

		for (Map.Entry<?, ?> entry : rawMap.entrySet()) {
			Object key = entry.getKey();
			Object value = entry.getValue();
			if (key instanceof String && value instanceof String[]) {
				paramMap.put((String) key, ((String[]) value)[0]);
			}
		}
		return paramMap;
	}

	/**
	 * 设置错误码，错误描述
	 * 
	 * @param view
	 * @param errorCode
	 */
	protected void setErrorMsg(MyGsonView view, String errorCode) {
		if (null != view && StringUtils.isNotBlank(errorCode)) {
			view.addStaticAttribute(BaseContants.RET_FLAG, BaseContants.FAILED);
			view.addStaticAttribute(BaseContants.ERROR_CODE, errorCode);
			view.addStaticAttribute(BaseContants.ERROR_MSG, ErrorCodeConstants.ERR_MAP.get(errorCode));
		}
	}
    
    /**
     * 业务异常统一处理
     * 
     * @param ex
     * @return
     */
    @ExceptionHandler(SawpException.class)
    @ResponseBody
    public MyGsonView sawpExceptionHandle(Exception ex) {
        MyGsonView view = new MyGsonView();
        view.addStaticAttribute(BaseContants.RET_FLAG, BaseContants.FAILED);
        view.addStaticAttribute(BaseContants.ERROR_CODE, BUSINESS_EXCEPTION);
        view.addStaticAttribute(BaseContants.ERROR_MSG, ex.getMessage());
        LOGGER.warn(ex.getMessage());
        return view;
    }
    
    /**
     * 系统异常统一处理
     * 
     * @param ex
     * @return
     */
    @ExceptionHandler(Exception.class)
    @ResponseBody
    @ResponseStatus(value = HttpStatus.INTERNAL_SERVER_ERROR)
    public MyGsonView exceptionHandle(Exception ex) {
        MyGsonView view = new MyGsonView();
        view.addStaticAttribute(BaseContants.RET_FLAG, BaseContants.FAILED);
        view.addStaticAttribute(BaseContants.ERROR_CODE, SYSTEM_EXCEPTION);
        view.addStaticAttribute(BaseContants.ERROR_MSG, ex.getMessage());
        LOGGER.error("occur exception：", ex);
        return view;
    }

	/**
	 * 
	 * 功能描述: 展示结果赋值,null 忽略<br>
	 * 
	 */
	protected <T> MyGsonView setGsonView(ReturnMsg<T> retMsg) {
		return setGsonView(retMsg, false);
	}

	/**
	 * 
	 * 功能描述: 展示结果赋值,字符串 null转成""<br>
	 */
	protected <T> MyGsonView setGsonViewWithEmpty(ReturnMsg<T> retMsg) {
		return setGsonView(retMsg, true);
	}

	private <T> MyGsonView setGsonView(ReturnMsg<T> retMsg, boolean nullToEmpty) {
		MyGsonView view = new MyGsonView(nullToEmpty);

		if (ReturnMsg.FAIL.equals(retMsg.getRetFlag())) {
			// 失败塞入相对应的错误码和错误信息
			view.addStaticAttribute(BaseContants.ERROR_CODE, retMsg.getErrorCode());
			view.addStaticAttribute(BaseContants.ERROR_MSG, retMsg.getErrorMessage());
		}
		view.addStaticAttribute(BaseContants.RET_FLAG, retMsg.getRetFlag());
		view.addStaticAttribute(BaseContants.DATA, retMsg.getData());

		return view;
	}

	/**
	 * 设置错误码，错误描述
	 * 
	 * @param view
	 * @param errorCode
	 * @param keys
	 *            多参数
	 */
	protected void setErrorMsg(MyGsonView view, String errorCode, Object... keys) {
		if (null != view && StringUtils.isNotBlank(errorCode)) {
			if (null == keys) {
				setErrorMsg(view, errorCode);
			} else {
				view.addStaticAttribute(BaseContants.RET_FLAG, BaseContants.FAILED);
				view.addStaticAttribute(BaseContants.ERROR_CODE, errorCode);
				MessageFormat form = new MessageFormat(ErrorCodeConstants.ERR_MAP.get(errorCode));
				view.addStaticAttribute(BaseContants.ERROR_MSG, form.format(keys));
			}
		}
	}
	
	protected boolean isFieldNull(String... args){
        for(String arg : args){
            if(StringUtils.isEmpty(arg)){
                return true;
            }
        }
        return false;
    }

}
